// collection.h	abstract class Collection

#ifndef _KC_COLLECTION__H_2008_KC_
#define _KC_COLLECTION__H_2008_KC_

#include <iostream>
#include <string>
#include <stdexcept>
#include <boost/shared_ptr.hpp>
 
namespace kc_sf
{

// zestaw wyjatków, specyficznych dla kolekcji i klas po niej
// dziedziczących, rzucanych jeśli zarządano dostępu do
// nieistniejącego elementu	
namespace Collection
{
	
class ElementError : public std::logic_error
{
	public:

		explicit ElementError( const std::string &msg = "" )
		: std::logic_error( "!!! Blad dostepu do elementu kolekcji" + msg )	{}
		
		virtual ~ElementError() throw() {}
};	

class PositionError : public ElementError
{
	public:

		explicit PositionError(	const std::string &coll_name = "" )
		: ElementError( createStr( coll_name ) )
		{}

		explicit PositionError(	std::size_t elem_pos,
								const std::string &coll_name = "" )
		: ElementError( createStr( coll_name, elem_pos ) )
		{}

	private:

		std::string createStr(	const std::string &coll_name,
								std::size_t elem_pos )	{
			std::string ret;

			if( !coll_name.empty() )
				ret += "\n\tKolekcja: " + coll_name;
			ret += "\n\tPoszukiwana pozycja: " + elem_pos;
			
			return ret;
		}

		std::string createStr( const std::string &coll_name )	{
			std::string ret;

			if( !coll_name.empty() )
				ret += "\n\tKolekcja: " + coll_name;
			ret += "\n\tKolekcja jest pusta";
			
			return ret;
		}
};

class NameError : public ElementError
{
	public:

		explicit NameError(	const std::string &elem_name,
							const std::string &coll_name = "" )
		: ElementError( createStr( coll_name, elem_name ) )
		{}

	private:
	
		std::string createStr(	const std::string &coll_name,
								const std::string &elem_name )	{
			std::string ret;

			if( !coll_name.empty() )
				ret += "\n\tKolekcja: " + coll_name;
			ret += "\n\tPoszukiwana nazwa: " + elem_name;
			
			return ret;
		}
};

const unsigned int npos = -1;

}

}

#endif // _KC_COLLECTION__H_2008_KC_


